﻿using ERPSystem.Common.Domains.Material;
using ERPSystem.Common.Domains.WarehouseCommon;
using ERPSystem.Common.DTO;
using ERPSystem.Common.Infrastructure.IRepository;
using MathNet.Numerics;
using MediatR;
using Mysqlx.Crud;
using SqlSugar;

namespace BasicInformationCommon.API.BasicInformationCommons.WarehouseReads
{
    public class WarehouseQueryHandler : IRequestHandler<WarehouseQueryCommand, Result<List<WarehouseQueryDto>>>
    {
        private readonly IBaseRepository<Warehouse> _warehouseRepository;
        private readonly IBaseRepository<ArrivalType> _arrivalTypeRepository;
        private readonly IBaseRepository<OutboundType> _outboundTypeRepository;
        private readonly IBaseRepository<InboundType> _inboundTypeRepository;
        private readonly IBaseRepository<MaterialCascade> _materialCascadeRepository;
        private readonly ISqlSugarClient _sqlSugarClient;

        public WarehouseQueryHandler(IBaseRepository<Warehouse> warehouseRepository, IBaseRepository<ArrivalType> arrivalTypeRepository, IBaseRepository<OutboundType> outboundTypeRepository, IBaseRepository<InboundType> inboundTypeRepository, IBaseRepository<MaterialCascade> materialCascadeRepository, ISqlSugarClient sqlSugarClient)
        {
            _warehouseRepository = warehouseRepository;
            _arrivalTypeRepository = arrivalTypeRepository;
            _outboundTypeRepository = outboundTypeRepository;
            _inboundTypeRepository = inboundTypeRepository;
            _materialCascadeRepository = materialCascadeRepository;
            _sqlSugarClient = sqlSugarClient;
        }
        /// <summary>
        /// 仓库列表业务逻辑
        /// </summary>
        /// <param name="request"></param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        public async Task<Result<List<WarehouseQueryDto>>> Handle(WarehouseQueryCommand request, CancellationToken cancellationToken)
        {
            var result = new Result<List<WarehouseQueryDto>>();
            try
            {
                var warehouse = await (await _warehouseRepository.GetAll()).ToListAsync();
                var arrivalType = await (await _arrivalTypeRepository.GetAll()).ToListAsync();
                var outboundType = await (await _outboundTypeRepository.GetAll()).ToListAsync();
                var inboundType = await (await _inboundTypeRepository.GetAll()).ToListAsync();
                var materialCascade = await (await _materialCascadeRepository.GetAll()).ToListAsync();
                var cc = (from a in warehouse
                          from value in a.MaterialTypeIds.Split(',')
                          from value1 in a.InBoundTypeId.Split(',')
                          from value2 in a.OutBoundTypeId.Split(',')
                          from value3 in a.ArrivalTypeId.Split(',')
                          join g in materialCascade on int.Parse(value) equals g.MaterialTypeId
                          join d in inboundType on int.Parse(value1) equals d.InboundTypeId
                          join c in outboundType on int.Parse(value2) equals c.OutboundTypeId
                          join b in arrivalType on int.Parse(value3) equals b.ArrivalTypeId
                          group new {a,b,c,d,g} by new {a.WarehouseId,a.RepositoryCode, a.WarehouseName, a.PeriodOfStorage, a.StartDate, a.StartCargoSpace, a.FormConfiguration, a.WarehouseKeeperId, a.OperatorId, a.CreatedOwnerId, a.CreatedTime, a.UpdatedOwnerId, a.UpdatedTime, a.DeletedOwnerId, a.DeletedTime} into e
                          select new WarehouseQueryDto()
                          {
                              WarehouseId = e.Key.WarehouseId,
                              RepositoryCode = e.Key.RepositoryCode,
                              WarehouseName = e.Key.WarehouseName,
                              PeriodOfStorage = e.Key.PeriodOfStorage,
                              StartDate = e.Key.StartDate,
                              StartCargoSpace = e.Key.StartCargoSpace,
                              FormConfiguration = e.Key.FormConfiguration,
                              WarehouseKeeperId = e.Key.WarehouseKeeperId,
                              OperatorId = e.Key.OperatorId,
                              MaterialTypeName = string.Join(",",e.Select(c => c.g.MaterialTypeName).Distinct()),
                              MaterialTypeIds = string.Join(",",e.Select(c=>c.g.MaterialTypeId)),
                              InBoundTypeName = string.Join(",", e.Select(c => c.d.InboundTypeName).Distinct()),
                              InBoundTypeIds = string.Join(",", e.Select(c => c.d.InboundTypeId)),
                              OutBoundTypeName = string.Join(",", e.Select(x => x.c.OutboundTypeName).Distinct()),
                              OutBoundTypeIds = string.Join(",", e.Select(x => x.c.OutboundTypeId)),
                              ArrivalTypeName = string.Join(",", e.Select(x => x.b.ArrivalTypeName).Distinct()),
                              ArrivalTypeIds = string.Join(",", e.Select(x => x.b.ArrivalTypeId)),
                              CreatedOwnerId = e.Key.CreatedOwnerId,
                              CreatedTime = e.Key.CreatedTime,
                              UpdatedOwnerId = e.Key.UpdatedOwnerId,
                              UpdatedTime = e.Key.UpdatedTime,
                              DeletedOwnerId = e.Key.DeletedOwnerId,
                              DeletedTime = e.Key.DeletedTime,
                          }).Distinct().ToList();
                result.Data = cc;
            }
            catch (Exception)
            {

                throw;
            }
            return result;
        }
    }
}
